package com.bf.hotpoint.service.impl;

import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;

import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.bf.hotpoint.common.SystemConfigValues;
import com.bf.hotpoint.domain.SimpleUser;
import com.bf.hotpoint.domain.User;
import com.bf.hotpoint.enums.ResultCodeEnum;
import com.bf.hotpoint.repository.mongo.MessageMongoRepository;
import com.bf.hotpoint.repository.mongo.UserMongoRepository;
import com.bf.hotpoint.repository.redis.CommonRedisRepository;
import com.bf.hotpoint.repository.redis.UserRedisRepository;
import com.bf.hotpoint.service.UserService;

@Service
public class UserServiceImpl implements UserService {
	
	static Logger log = Logger.getLogger(UserService.class.getName());
	
	@Autowired
	private UserMongoRepository userMongoRepository;
	
	@Autowired
	private MessageMongoRepository messageMongoRepository;
	
	@Autowired
	private UserRedisRepository redisRepository;
	
	@Autowired
	private CommonRedisRepository commonRedis;
	
	private Date getExpireDate(){
		Calendar c=new GregorianCalendar();
		c.add(Calendar.MONTH, 24);
		return c.getTime();
	}
	
	public ResultCodeEnum initUser(String uuid,String deviceToken)
	{
		if(uuid == null || uuid.isEmpty())
		{
			return ResultCodeEnum.PARAMETER_IS_NULL;
		}
		
		User user = new User();
		user.setAvailable(true);
		user.setUuid(uuid);
		user.setDeviceToken(deviceToken);
		user.setReport(0);
		user.setReported(0);
		
		//init redis
		try {
			redisRepository.setUser(user, this.getExpireDate());
		} catch (Exception e) {
			log.error(e);
			System.out.println(e);
		}
		log.info("user register to redis successfully uuid:"+uuid);
		System.out.println("user register to redis successfully uuid:"+uuid);
		return ResultCodeEnum.SUCCESS;
	}
	
	public User getAvailableUser(String uuid){
		User user = this.getUserByUuid(uuid);
		if(user != null && user.isAvailable() != false)
		{
			return user;
		}
		return null;
	}
	
	public User getUserByUuid(String uuid){
		
		User user = redisRepository.getUserByUuid(uuid);
		if(user == null)
		{
			this.initUser(uuid,null);
			return this.getUserByUuid(uuid);
		}
		return user;
		
		/**
		User user = redisRepository.getUserByUuid(uuid);
		if(user == null)
		{
			user = userMongoRepository.getUser(uuid);
			if(user != null)
			{
				redisRepository.setUser(user, this.getExpireDate());	
			}
			else
			{
				this.initUser(uuid);
				return this.getUserByUuid(uuid);
			}
		}
		return user;
		*/
	}
	
	public boolean isAvailable(String uuid){
		User user = this.getUserByUuid(uuid);
		return user.isAvailable();
		
	}
	
	public boolean setReportedAndReport(String reportUuid,String reportedUuid)
	{
		boolean isReportedAndReportSuccess = false;
		try {
			boolean isReportSuccess = this.setUsersReport(reportUuid);
			if(isReportSuccess)
				isReportedAndReportSuccess = this.setUsersReported(reportedUuid);
		} catch (Exception e) {
			log.error(e);
		}
		return isReportedAndReportSuccess;
	}
	
	public boolean setUsersReported(String uuid)
	{
		User user = this.getAvailableUser(uuid);
		if(user == null)
		{
			return false;
		}
		user.setReported(user.getReported()+1);
		if(user.getReported() >= SystemConfigValues.INSTANCE.maxReportedOfUser)
		{
			user.setAvailable(false);
		}
		redisRepository.setUser(user, this.getExpireDate());
		commonRedis.setOperationUsers(user.getUuid());
		return true;
	}
	
	public boolean setUsersReport(String uuid)
	{
		User user = this.getAvailableUser(uuid);
		if(user == null)
		{
			return false;
		}
		user.setReport(user.getReport()+1);
		if(user.getReport() >= SystemConfigValues.INSTANCE.maxReportOfUser)
		{
			return false;
		}
		redisRepository.setUser(user, this.getExpireDate());
		commonRedis.setOperationUsers(user.getUuid());
		return true;
	}

	
	public User printUser(String uuid)
	{
		System.out.println(this.getUserByUuid(uuid));
		return this.getUserByUuid(uuid);
	}
	
	public void saveUserToMongo(String uuid,String nickName,boolean sex)
	{
		SimpleUser su = new SimpleUser();
		su.setUuid(uuid);
		su.setNickName(nickName);
		su.setSex(sex);
		userMongoRepository.addSimpleUser(su);
	}
	
	public SimpleUser getUserFromMongo(String uuid)
	{
		return userMongoRepository.getSimpleUser(uuid);
	}
}
